#include <bits/stdc++.h>

using namespace std;

typedef long long ll;

const int N = 1e5 + 5;
const int M = 1e9 + 7;

struct Edge
{
    int to, next;
} e[N << 1];

int head[N], idx = 1, a[N], n;
int dp[N];

void add_edge(int u, int v)
{
    e[idx].to = v;
    e[idx].next = head[u];
    head[u] = idx++;
}
void clear_graph()
{
    memset(head, -1, sizeof(head));
    memset(e, 0, sizeof(e));
    idx = 1;
}

multiset<int> s1, s2;
     
void adjust()
{
    if (s1.size())
    {
        auto it = s1.end();
        it--;
        s2.insert(*it), s1.erase(it);
    }

    while (s1.size() < s2.size())
    {
        auto it = s2.begin();
        s1.insert(*it);
        s2.erase(it);
    }
}

void insert(int x)
{
    s1.insert(x);
    adjust();
}

void remove(int x)
{
    auto it = s1.end();
    it--;

    if (*it < x)
        s2.erase(s2.find(x));
    else
        s1.erase(s1.find(x));

    adjust();
}

int get_median()
{
    auto it = s1.end();
    it--;

    if (s1.size() == s2.size() + 1)
        return *it;
    else
        return (*it + *s2.begin()) >> 1;
}


void dfs(int u, int fa = -1, int dep = 1)
{
    insert(a[u]);
    int Max = 0, Min = INT_MAX;
    bool leaf = true;

    for (int i = head[u]; ~i; i = e[i].next) {
        int j = e[i].to;

        if (j != fa) {
            leaf = false;
            dfs(j, u, dep+1);
            Max = max(dp[j], Max), Min = min(dp[j], Min);
        }
    }

    if (leaf) dp[u] = get_median();
    else if (dep&1) dp[u] = Max;
    else dp[u] = Min;

    remove(a[u]);
}
int main()
{
#ifdef LOCAL
    freopen("in.txt", "r", stdin);
    freopen("out.txt", "w", stdout);
#endif
    ios::sync_with_stdio(false), cin.tie(0);
    clear_graph();

    cin >> n;

    for (int i = 1; i <= n; i++)
    {
        cin >> a[i];
    }

    for (int i = 0; i < n - 1; i++)
    {
        int u, v;
        cin >> u >> v;
        add_edge(u, v), add_edge(v, u);
    }

    dfs(1);

    cout << dp[1] << endl;
    return 0;
}